import codecs
import csv
import json
import re


class CargoDataSource:

    def load(self, input_file_path):
        # errors = {}
        with codecs.open(input_file_path, encoding='utf-8-sig') as f:
            # index_list = []
            # list_results = []
            row_datas = []
            for row in csv.DictReader(f, skipinitialspace=True):
                row_datas.append(row)
        return row_datas


    def csv_data_check(self, check_row, index_list):
        check_col1, check_col2, check_col3, check_col4 = \
            check_row["weight"], check_row["dimensions"], check_row["destination"], check_row["index"]
        check_col1_res = self.weight_check(check_col1)
        check_col2_res = self.dimensions_check(check_col2)
        check_col3_res = self.destination_check(check_col3)
        check_col4_res = self.index_check(check_col4, index_list)
        check_row["errors"], check_row["remarks"] = {}, {}
        # row["errors"], row["remarks"] = {"错误": "打印错误信息"}, {"备注信息": "打印备注信息"}

        if not check_col1_res:
            check_row["errors"].update({"weight":"（重量）值必须大于 10。单位是可选的，但“kg”是唯一允许的单位"})
        if not check_col2_res:
            check_row["errors"].update({"dimensions":"（尺寸）由“\*”字符分隔。单位是必需的，“cm”和“mm”是唯一允许的两个单位，但不能同时使用（所以1cm\*2cm\*3mm无效）。每个维度值必须大于 0。"})
        if not check_col3_res:
            check_row["remarks"].update({"destination":"(目的地) 是可选填的"})
        if not check_col4_res:
            check_row["errors"].update({"index":"（索引）必须唯一"})

        print(check_row)

    def weight_check(self, weight_data):
        res_num = re.findall(r"[0-9]+", weight_data)
        res = re.findall(r"[A-FH-JL-Za-fh-jl-z]+", weight_data)
        if len(res_num) == 0:
            res_num = '0'
        if int(res_num[0]) <= 10 or len(res)>0:
            return False
        else:
            return res_num[0]

    def dimensions_check(self, dimensions_data):
        res_dim_unit = re.findall(r"[cm|mm]+", dimensions_data)
        res_num = re.findall(r"[0-9]+", dimensions_data)
        if len(res_dim_unit) < 3 or ('cm' in res_dim_unit and 'mm' in res_dim_unit):
            return False
        else:
            return [res_num,res_dim_unit]

    def destination_check(self, destination_data):
        if not destination_data:
            return False
        else:
            return True

    def index_check(self, index_data, index_list):
        if index_data in index_list:
            return False
        else:
            index_list.append(index_data)
            return index_list

    def datas_transfer(self, row, index_list, list_results):
        dimensions_res = self.dimensions_check(row["dimensions"])
        # print(dimensions_res)
        weight_res = self.weight_check(row["weight"])
        # print(weight_res)
        index_res = self.index_check(row["index"], index_list)
        # print(index_res,index_list)
        # res_num = re.findall(r"[0-9]+", row["dimensions"])
        # res = re.findall(r"[A-FH-JL-Za-fh-jl-z]+", row["weight"])
        if dimensions_res and weight_res and index_res:
            # if res and index_res:
            #     print(res_num)
            dim_unit = dimensions_res[1][0]
            # dim_unit = row["dimensions"].split("*")[0][-2:]
            new_dict = {}
            new_dict.update(
                {"weight": int(weight_res), "length": int(dimensions_res[0][0]), "width": int(dimensions_res[0][1]),
                 "height": int(dimensions_res[0][2]),
                 "dim_unit": dim_unit, "destination": row["destination"], "index": int(row["index"])})
            list_results.append(new_dict)

        return list_results

    def export(self, output_file_path, load_dict):
        with open(output_file_path, "w") as f:
            json.dump(load_dict, f, indent=4, ensure_ascii=False)
        print("Finished.")

    def datas_diff(self, source_1, source_2):
        diff_list = [item for item in source_1 if item not in source_2]
        return diff_list

if __name__ == '__main__':
    res = CargoDataSource()
    cc = res.load(r'C:\softtest\web_python\advanced\data_sources\cargo.csv')
    # print(cc)
    obj_dict = []
    for i in cc:
        res.csv_data_check(i, index_list = [])
        load_dict = res.datas_transfer(i, index_list=[], list_results=[])
        # print(type(load_dict))
        obj_dict.extend(load_dict)
    # print((obj_dict))
    res.export('ss.json', load_dict=obj_dict)
    source_1 = [
        {"weight": 30, "length": 1, "width": 2, "height": 3,
         "dim_unit": "cm", "destination": "SZ", "index": 1},
        {"weight": 16, "length": 4, "width": 2, "height": 1,
         "dim_unit": "cm", "destination": "SZ", "index": 2},
        {"weight": 15, "length": 4, "width": 2, "height": 1,
         "dim_unit": "cm", "destination": "SZ", "index": 2}
    ]
    source_2 = [
        {"weight": 30, "length": 1, "width": 2, "height": 3,
         "dim_unit": "cm", "destination": "SZ", "index": 1},
        {"weight": 16, "length": 8, "width": 4, "height": 2,
         "dim_unit": "mm", "destination": "HZ", "index": 2},
        {"weight": 16, "length": 4, "width": 2, "height": 1,
         "dim_unit": "mm", "destination": "SZ", "index": 2}
    ]
    print(res.datas_diff(source_1, source_2))